home *** CD-ROM | disk | FTP | other *** search
/ Cream of the Crop 22 / Cream of the Crop 22.iso / program / cgazv3n4.zip / ROOT-DIR.ZIP / NEWTOUCH.C < prev    next >
C/C++ Source or Header  |  1989-04-16  |  9KB  |  307 lines

  1. /***************************** NEWTOUCH.C *************************
  2. *   Program to expand the functions of the Unix 'touch' utility
  3. *
  4. *   Usage:   newtouch  filename  new-date new-time
  5. *
  6. *            filename may contain wildcards. With wildcards, all
  7. *                     matching files will be set to the specified
  8. *                     date and time. With no wildcards, only the
  9. *                     specified file is set; if the file does not
  10. *                     exist, it is created.
  11. *            new-date [optional]  date in the format MM/DD/YY
  12. *                     YY is 20th century; if not specified,
  13. *                     the existing file date is used
  14. *            new-time [optional]  time in the format HH:MM:SS
  15. *                     uses a 24-hour clock; if not specified,
  16. *                     the existing file time is used.
  17. *
  18. *            Note: if time and date are omitted, the current time
  19. *                  and date are used.
  20. *
  21. *   Copyright (c) 1989 Andrew Binstock. May be distributed as is
  22. *   as long as no fee of any kind is charged. C Gazette, Spring 1989
  23. *******************************************************************/
  24.  
  25. /* OK for Microsoft and Turbo. For Microsoft, you must #define MSC */
  26.  
  27. /* #define MSC 1 */
  28.  
  29. #include <stdio.h>
  30. #include <dos.h>
  31. #include <stdlib.h>
  32. #include <string.h>
  33.  
  34. #if __TURBOC__
  35. #include <dir.h>
  36. #endif
  37.  
  38. #define YES  1
  39. #define NO   0
  40.  
  41. int hh, min, ss,
  42.     yy, mm,  dd,
  43.     wildcards;
  44.  
  45. FILE *touch_me;
  46.  
  47. void show_usage(void),
  48.      current_date_and_time(void),
  49.      set_file_date_time (int, char *);
  50.  
  51. int  get_file_name  (char *, char *),
  52.      get_next_name (char *, char *);
  53.  
  54. int  time_specified,    /* Switched to YES if true */
  55.      date_specified;
  56.  
  57. main (int argc, char *argv[])
  58. {
  59.     int i;
  60.  
  61.     if (argc < 2)
  62.     {
  63.         show_usage();
  64.         exit (5);
  65.     }
  66.  
  67.     wildcards = (((strpbrk (argv[1], "?*")) == NULL) ? NO : YES);
  68.  
  69.     for (i = 2; i < argc; i++)
  70.     {
  71.         if (strchr (argv[i], ':') != NULL)      /* time found */
  72.         {
  73.             sscanf(argv[i], "%d:%d:%d", &hh, &min, &ss);
  74.             time_specified = YES;
  75.         }
  76.         else
  77.         if (strpbrk (argv[i], "/-") != NULL)    /* date found */
  78.         {
  79.             char c;
  80.             sscanf (argv[i], "%d%c%d%c%d", &mm, &c, &dd, &c, &yy);
  81.             date_specified = YES;
  82.         }
  83.         else
  84.         {
  85.             show_usage();
  86.             exit (6);
  87.         }
  88.     }   /* end of argument scan */
  89.  
  90.     for (;;)
  91.     {
  92.         char filename[80];
  93.  
  94.         if (get_file_name (filename, argv[1]) == NO) /*If no more files, quit */
  95.             break;
  96.         else
  97.         {
  98.             if (wildcards == NO) /* Files can only be created if = NO */
  99.             {                    /* so create file as needed.         */
  100.                 if ((touch_me = fopen (filename, "r")) == NULL)
  101.                 {
  102.                     if ((touch_me = fopen (filename, "w")) == NULL)
  103.                     {
  104.                         fprintf (stderr, "Cannot create %s\n", filename);
  105.                         exit (7);
  106.                     }
  107.                 }
  108.             }
  109.             else
  110.             {
  111.                 if ((touch_me = fopen (filename, "r")) == NULL)
  112.                 {
  113.                     fprintf (stderr, "Cannot open %s\n", filename);
  114.                     continue;
  115.                 }
  116.             }
  117.  
  118.             /* At this point, the file is open */
  119.  
  120.             set_file_date_time (fileno(touch_me), filename);
  121.             fclose (touch_me);
  122.         }
  123.     }   /* end of file names - fall through to exit */
  124.  
  125.     exit (0);
  126. }
  127.  
  128. int get_file_name(char *name, char *spec)    /* Get name of next file */
  129. {
  130.     static int no_more = NO;
  131.  
  132.     if (no_more)
  133.         return NO;
  134.  
  135.     if (wildcards == NO)
  136.     {
  137.         strcpy (name, spec);    /* No wildcards, use the name as is */
  138.         no_more = YES;          /* and stop file name generation.   */
  139.         return (YES);
  140.     }
  141.     else
  142.     {
  143.         if (get_next_name (name, spec) == NO)
  144.         {
  145.             no_more = YES;          /* No more matching files */
  146.             return (NO);
  147.         }
  148.         else
  149.             return (YES);           /* Matching files still found */
  150.     }
  151. }
  152.  
  153. int get_next_name (char *name, char *spec)/* Get next matching wildcard name */
  154. {
  155.  
  156. #define NO_MORE  -1
  157.  
  158.     static struct ffblk {
  159.         char reserved [21];
  160.         char attribute;
  161.         unsigned write_time;
  162.         unsigned write_date;
  163.         long sizeof_file;
  164.         char ff_name [13];
  165.         }
  166.              file_info;     /* structure to hold file match info */
  167.     static int been_here = NO;
  168.  
  169.     if (been_here == NO)        /* On first time, do findfirst() */
  170.     {
  171. #if __TURBOC__
  172.         if (findfirst (spec, &file_info, 0) == NO_MORE)
  173. #elif MSC
  174.         if (_dos_findfirst (spec, 0x7F, &file_info) != 0)
  175. #endif
  176.             return (NO);
  177.         else
  178.             strcpy (name, file_info.ff_name);
  179.  
  180.         been_here = YES;
  181.         return (YES);
  182.     }
  183.     else
  184.     {
  185. #if __TURBOC__
  186.         if (findnext (&file_info) == NO_MORE)
  187. #elif MSC
  188.         if (_dos_findnext (&file_info) != 0)
  189. #endif
  190.             return (NO);
  191.         else
  192.         {
  193.             strcpy (name, file_info.ff_name);
  194.             return (YES);
  195.         }
  196.     }
  197. }
  198.  
  199. void set_file_date_time (int file_handle, char *name)
  200. {
  201.     /* First, get the file's present date and time,
  202.        then overlay with any specified date and time */
  203.  
  204.     union REGS inreg, outreg;
  205.  
  206.     struct set_time {               /* Bit fields  */
  207.         unsigned set_sec:  5;       /* seconds / 2 */
  208.         unsigned set_min:  6;       /* minutes     */
  209.         unsigned set_hrs:  5;       /* hours       */
  210.         }
  211.             st;
  212.  
  213.      struct set_date {
  214.         unsigned set_day:  5;       /* day of month*/
  215.         unsigned set_mon:  4;       /* month       */
  216.         unsigned set_yr:   7;       /* year - 1980 */
  217.         }
  218.             sd;
  219.  
  220.     /* Get the file's present date and time */
  221.  
  222.     inreg.h.ah = 0x57;      /* function for get/set file date and time */
  223.     inreg.h.al = 0x00;      /* get */
  224.     inreg.x.bx = file_handle;
  225.     int86 (0x21, &inreg, &outreg);
  226.  
  227.     st = *(struct set_time *) &outreg.x.cx;
  228.     sd = *(struct set_date *) &outreg.x.dx;
  229.  
  230.     /* If nothing specified, use the current date and time */
  231.  
  232.     if (!time_specified && !date_specified)
  233.     {
  234.         current_date_and_time();
  235.         st.set_sec = ss / 2;
  236.         st.set_min = min;
  237.         st.set_hrs = hh;
  238.         sd.set_day = dd;
  239.         sd.set_mon = mm;
  240.         sd.set_yr  = yy - 1980;
  241.      }
  242.  
  243.     /* If something specified, use that */
  244.  
  245.     if (time_specified)               /* If a time was specified,  */
  246.     {                                 /* use it, else use defaults */
  247.         st.set_sec = ss / 2;
  248.         st.set_min = min;
  249.         st.set_hrs = hh;
  250.     }
  251.  
  252.     if (date_specified)               /* If a date was specified,   */
  253.     {                                 /* use it, else use defaults  */
  254.         sd.set_day = dd;
  255.         sd.set_mon = mm;
  256.         sd.set_yr  = (yy - 80);
  257.     }
  258.  
  259.     /* At last, set the values */
  260.  
  261.     inreg.h.ah = 0x57;      /* function for get/set file date and time */
  262.     inreg.h.al = 0x01;      /* set */
  263.     inreg.x.bx = file_handle;
  264.     inreg.x.cx = * ((unsigned int *) &st);
  265.     inreg.x.dx = * ((unsigned int *) &sd);
  266.  
  267.     int86 (0x21, &inreg, &outreg);
  268.  
  269.     printf ("%s set to %02d-%02d-%02d %02d:%02d:%02d\n", name,
  270.             sd.set_mon, sd.set_day, sd.set_yr,
  271.             st.set_hrs, st.set_min, st.set_sec);
  272. }
  273.  
  274. void current_date_and_time (void)  /* Get them */
  275. {
  276. #if __TURBOC__
  277.     struct date curr_date;
  278.     struct time curr_time;
  279.  
  280.     getdate (&curr_date);
  281.     gettime(&curr_time);
  282.  
  283.     yy = curr_date.da_year; mm = curr_date.da_mon; dd = curr_date.da_day;
  284.     hh = curr_time.ti_hour; min= curr_time.ti_min; ss = curr_time.ti_sec;
  285.  
  286. #elif MSC
  287.     struct dosdate_t curr_date;
  288.     struct dostime_t curr_time;
  289.  
  290.     _dos_getdate (&curr_date);
  291.     _dos_gettime (&curr_time);
  292.  
  293.     yy = curr_date.year; mm = curr_date.month; dd = curr_date.day;
  294.     hh = curr_time.hour; min= curr_time.minute; ss = curr_time.second;
  295. #endif
  296. }
  297.  
  298. void show_usage(void)        /* Explain specification format */
  299. {
  300.     fputs ("Usage: newtouch filename new-date new-time\n"      , stderr);
  301.     fputs ("  filename may contain wildcards\n"                , stderr);
  302.     fputs ("  date is optional using MM/DD/YY or MM-DD-YY\n"   , stderr);
  303.     fputs ("  time is optional using HH:MM:SS and 24-hr. clock", stderr);
  304. }
  305.  
  306.  
  307.